#include <iostream>
#include <typeinfo>

using namespace std;

//类模板对象做函数参数
//类模板实例化出的对象，向函数传参的方式
//一共有三种传入方式：
//1. 指定传入的类型   --- 直接显示对象的数据类型
//2. 参数模板化      --- 将对象中的参数变为模板进行传递
//3. 整个类模板化     --- 将这个对象类型 模板化进行传递
//使用比较广泛是第一种：指定传入的类型

template<typename NameType, class AgeType>
class Person {
public:
    NameType name;
    AgeType age;

    Person(NameType name, AgeType age) {
        this->name = name;
        this->age = age;
    }

    void showPerson() {
        cout << "name:" << this->name << ",age:" << this->age << endl;
    }
};

//1. 指定传入的类型
void print1(Person<string, int> &p) {
    p.showPerson();
}

void test1() {
    Person<string, int> person("张三", 18);
    print1(person);
}

//2. 参数模板化
template<typename NameType, typename AgeType>
void print2(Person<NameType, AgeType> &p) {
    p.showPerson();
    cout << "NameType:" << typeid(NameType).name() << endl;
    cout << "AgeType:" << typeid(AgeType).name() << endl;
}

void test2() {
    Person<string, int> person("李四", 19);
    print2(person);
}

//3. 整个类模板化
template<typename T>
void print3(T &p) {
    p.showPerson();
    cout << "T:" << typeid(T).name() << endl;
}

void test3() {
    Person<string, int> person("王五", 20);
    print3(person);
}

int main() {
    test1();
    test2();
    test3();
    return 0;
}